using System;
using System.Collections.Generic;
using System.IO;
using System.IO.IsolatedStorage;
using System.Linq;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;

namespace System.IO.IsolatedStorage
{
    public class PSFileInfo : AbstractFileInfo//: FileSystemInfo
    {
        string originalfileName;
        string cleanedfileName;

        public PSFileInfo(string fileName)
        {
            originalfileName = PSDirectory.FixRelativePath(fileName);
            cleanedfileName = (originalfileName.StartsWith(@"\") ? originalfileName.Substring(1) : originalfileName);
        }

        public override AbstractDirectoryInfo Directory
        {
            get
            {
                return new PSDirectoryInfo(DirectoryName);
            }
        }

        public override string DirectoryName
        {
            get
            {
                var temp = PSDirectory.FixRelativePath(originalfileName);
                var place = temp.LastIndexOf('\\');
                if (place == -1)
                    return temp;
                return temp.Substring(0, place);
            }
        }

        public override bool Exists
        {
            get
            {
                return PSFile.Exists(originalfileName);
            }
        }

        public override long Length
        {
            get
            {
                return PSFile.FileLength(originalfileName);
            }
        }

        public override string Name
        {
            get
            {
                return System.IO.Path.GetFileName(originalfileName);
            }
        }

        //public PSFileInfo LocalFile
        //{
        //    get
        //    {
        //        return this;
        //    }
        //}

        public override string FullName
        {
            get
            {
                return originalfileName;
            }
        }

        public override StreamWriter AppendText()
        {
            return PSFile.AppendText(originalfileName);
        }

        public override AbstractFileInfo CopyTo(string destFileName)
        {
            PSFile.Copy(originalfileName, destFileName);
            return new PSFileInfo(PSDirectory.FixRelativePath(destFileName));
        }

        public override AbstractFileInfo CopyTo(string destFileName, bool overwrite)
        {
            PSFile.Copy(originalfileName, destFileName, overwrite);
            return new PSFileInfo(PSDirectory.FixPath(destFileName));
        }

        public override Stream Create()
        {
            return PSFile.Create(originalfileName);
        }

        public override StreamWriter CreateText()
        {
            return PSFile.CreateText(originalfileName);
        }

        public override void Delete()
        {
            PSFile.Delete(originalfileName);
        }

        public override void MoveTo(string destFileName)
        {
            PSFile.Move(originalfileName, destFileName);
            originalfileName = PSDirectory.FixPath(destFileName);
        }

        public override Stream Open(FileMode mode)
        {
            return PSFile.Open(originalfileName, mode);
        }

        public override Stream Open(FileMode mode, FileAccess access)
        {
            return PSFile.Open(originalfileName, mode, access);
        }

        public override Stream Open(FileMode mode, FileAccess access, FileShare share)
        {
            return PSFile.Open(originalfileName, mode, access, share);
        }

        public override Stream OpenRead()
        {
            return PSFile.OpenRead(originalfileName);
        }

        public override StreamReader OpenText()
        {
            return PSFile.OpenText(originalfileName);
        }

        public override Stream OpenWrite()
        {
            return PSFile.OpenWrite(originalfileName);
        }

        public override string ToString()
        {
            return originalfileName;
        }

        public override void CreateAsync(Action<Stream, Exception> callback)
        {
            Stream stream = null;
            try
            {
                stream = Create();
                callback(stream, null);
            }
            catch (Exception ex)
            {
                if (stream != null)
                {
                    stream.Close();
                    stream = null;
                }
                callback(null, ex);
            }
        }

        public override void OpenReadAsync(Action<Stream, Exception> callback)
        {
            Stream stream = null;
            try
            {
                stream = OpenRead();
                callback(stream, null);
            }
            catch (Exception ex)
            {
                if (stream != null)
                {
                    stream.Close();
                    stream = null;
                }
                callback(null, ex);
            }
        }

        public override void OpenTextAsync(Action<StreamReader, Exception> callback)
        {
            StreamReader stream = null;
            try
            {
                stream = OpenText();
                callback(stream, null);
            }
            catch (Exception ex)
            {
                if (stream != null)
                {
                    stream.Close();
                    stream = null;
                }
                callback(null, ex);
            }
        }

        public override void OpenWriteAsync(Action<Stream, Exception> callback)
        {
            Stream stream = null;
            try
            {
                stream = OpenWrite();
                callback(stream, null);
            }
            catch (Exception ex)
            {
                if (stream != null)
                {
                    stream.Close();
                    stream = null;
                }
                callback(null, ex);
            }
        }

        public override void OpenAsync(FileMode mode, FileAccess access, FileShare share, Action<Stream, Exception> callback)
        {
            Stream stream = null;
            try
            {
                stream = Open(mode, access, share);
                callback(stream, null);
            }
            catch (Exception ex)
            {
                if (stream != null)
                {
                    stream.Close();
                    stream = null;
                }
                callback(null, ex);
            }
        }

        public override void OpenAsync(FileMode mode, FileAccess access, Action<Stream, Exception> callback)
        {
            Stream stream = null;
            try
            {
                stream = Open(mode, access);
                callback(stream, null);
            }
            catch (Exception ex)
            {
                if (stream != null)
                {
                    stream.Close();
                    stream = null;
                }
                callback(null, ex);
            }
        }

        public override void OpenAsync(FileMode mode, Action<Stream, Exception> callback)
        {
            Stream stream = null;
            try
            {
                stream = Open(mode);
                callback(stream, null);
            }
            catch (Exception ex)
            {
                if (stream != null)
                {
                    stream.Close();
                    stream = null;
                }
                callback(null, ex);
            }
        }

        public override void MoveToAsync(string destFileName, Action<Exception> callback)
        {
            try
            {
                MoveTo(destFileName);
                callback(null);
            }
            catch (Exception ex)
            {
                callback(ex);
            }
        }

        public override void CreateTextAsync(Action<StreamWriter, Exception> callback)
        {
            try
            {
                callback(CreateText(), null);
            }
            catch (Exception ex)
            {
                callback(null, ex);
            }
        }

        public override bool SupportsAsync
        {
            get { return true; }
        }

        public override bool SupportSync
        {
            get { return true; }
        }

        public override void DeleteAsync(Action<Exception> errorCallback)
        {
            try
            {
                Delete();
                errorCallback(null);
            }
            catch (Exception ex)
            {
                errorCallback(ex);
            }
            errorCallback(null);
        }

        public override void GetExistsAsync(Action<bool> callback)
        {
            callback(Exists);
        }

        public override void LoadInfo(Action<bool> callback)
        {
            callback(true); // no need to do anything
        }
    }
}